#include "dominion.h"
#include "dominion_helpers.h"
#include <string.h>
#include <stdio.h>
#include <assert.h>
#include "rngs.h"

#define DEBUG 0
#define NOISY_TEST 1

int showhand(struct gameState state, int player) {
	int i;
	printf("=======Player %d's Hand=======", player);
	for (i = 0; i < state.handCount[player]; i++) {
		printf("%d ", state.hand[player][i]);
	}
	printf("\n");

	return 0;
}

int showdeck(struct gameState state, int player) {
	int i;
	printf("=======Player %d's Deck=======", player);
	for (i = 0; i < state.deckCount[player]; i++) {
		printf("%d ", state.deck[player][i]);
	}
	printf("\n");

	return 0;
}

int showdiscard(struct gameState state, int player) {
	int i;
	printf("=======Player %d's Discard Pile=======", player);
	for (i = 0; i < state.discardCount[player]; i++) {
		printf("%d ", state.discard[player][i]);
	}
	printf("\n");

	return 0;
}

int main(int argc, char **argv) {
	int i, j;
	int over;	//For gameover check
	int k[10];	//Array for kingdom cards
	int winners[4];
	struct gameState G;
	
	PutSeed(-1);

	int players = (Random() * 2) + 2;
	int seeder = Random() * 1000000;
	int randnum;

	int actionCards;
	int choice1, choice2, choice3 = 0;	
	int currCard;
	int curTurn;
	int handpos;
	int turnNum = 0;
	
	//Randomly generate 10 kingdom cards for the game
	int dup = 0;		// Flag to check if a kingdom card already is chosen
	for (i = 0; i < 10; i++) {
		randnum = adventurer + floor((Random() * 20));
		if (randnum == 27) {
			randnum = 26;
		}
			for (j = 0; j < i; j++) {
				if (k[j] == randnum){
					dup = 1;
				}
			}
			while (dup == 1){
				randnum = adventurer + floor((Random() * 20));
				if (randnum == 27) {
					randnum = 26;
				}
				dup = 0;
				for (j = 0; j < i; j++) {
					if (k[j] == randnum){
						dup = 1;
					}
				}
			}
		k[i] = randnum;
	}

	
	over = initializeGame(players, k, seeder, &G);
	assert(over == 0);

	//Print statements
	printf("=======Game Start=======\n");
	printf("Number of Players: %d\n", players);
	
	//Prints all kingdom cards for the game
	printf("Kingdom Cards: ");
	for (i = 0; i < 10; i++) {
		printf("%d ", k[i]);
	}
	printf("\n");

	printf("Random Seed: %d\n", seeder);
	printf("\n=======Beginning Phase=======\n");
	for (i = 0; i < players; i++) {
		showhand(G, i);
		showdeck(G, i);
		showdiscard(G, i);
		printf("\n");
	}

	while(1) {
		turnNum++;
		curTurn = whoseTurn(&G);
		actionCards = 0;

		printf("\n\n======= Turn: %d  Player: %d =======\n", turnNum, curTurn);
		for (i = 0; i < players; i++) {
			showhand(G, i);
			showdeck(G, i);
			showdiscard(G, i);
		}

		for (i = 0; i < G.handCount[curTurn]; i++) {
			if (G.hand[curTurn][i] > gold) {
				actionCards++;
			}
		}

		printf("=======Player %d's turn=======\n", curTurn);
		printf("Number of actions: %d\n", G.numActions);
		printf("Number of buys: %d\n", G.numBuys);
		printf("Number of coins: %d\n", G.coins);

		//Action Phase
		printf("\n\n=======Action Phase=======\n");
		while(G.numActions !=0 && actionCards != 0) {
			printf("Number of actions: %d\n", G.numActions);

			if (floor(Random() * 100) < 20) {
				break;
			}
			
			for (i = 0; i < G.handCount[curTurn]; i++) {
				if (G.hand[curTurn][i] > gold) {
					currCard = G.hand[curTurn][i];
					handpos = i;
				}
			}

			switch(currCard) {
				case feast:
					choice1 = floor((Random() * 27));
					if (choice1 == 27) {
						choice1 = 26;
					}
					break;
				case mine:
					choice1 = floor(Random()*(G.handCount[curTurn]));
					if (choice1 == G.handCount[curTurn]) {
						choice1 = G.handCount[curTurn] - 1;	
					}
					while (choice1 == handpos) {
						choice1 == floor(Random()*(G.handCount[curTurn]));	
					}
					choice2 = floor((Random()*2) + copper);
					break;
				case remodel:
					choice1 = floor(Random()*(G.handCount[curTurn]-1));
					if (choice1 == G.handCount[curTurn]) {
						choice1 = G.handCount[curTurn] - 1;	
					}
					while (choice1 == handpos) {
						choice1 == floor(Random()*(G.handCount[curTurn]));	
					}
					choice2 = floor(Random()*27);
					if (choice2 == 27) {
						choice2 = 26;
					}
					break; 
				case baron:
					choice1 = floor(Random()*2);
					if (choice1 == 2) {
						choice1 = 1;
					}
					break;
				case minion:
					choice1 = floor(Random()*2) + 1;
					if (choice1 == 3) {
						choice1 = 2;
					}
					break;
				case steward:
					choice1 = floor(Random()*3) + 1;
					if (choice1 == 4) {
						choice1 = 3;	
					}
					if (choice1 == 3) {
						choice2 = floor(Random()*(G.handCount[curTurn]));
						if (choice2 == G.handCount[curTurn]){
							choice2 = G.handCount[curTurn]-1;
						}	
						choice3 = floor(Random()*(G.handCount[curTurn]));
						if (choice1 == G.handCount[curTurn]){
							choice1 = G.handCount[curTurn] - 1;
						}
					}
					break;
				case ambassador:
					choice1 = floor(Random()*(G.handCount[curTurn]-1));
					if (choice1 == G.handCount[curTurn]) {
						choice1 = G.handCount[curTurn]-1;
					}
					choice2 = floor((Random()*2) + 1);
					if (choice2 == 3) {
						choice2 = 2;	
					}
					break;
				case embargo:
					choice1 = floor(Random()*27);
					if (choice1 == 27) {
						choice1 = 26;
					}
					break;
				case salvager:
					choice1 = floor(Random()*(G.handCount[curTurn]));
					if (choice1 == G.handCount[curTurn]){
						choice1 = G.handCount[curTurn]-1;	
					}
					break;
			}
			printf("\nPlayer %d is trying to play %d", curTurn, currCard);
			printf(" with %d %d %d as choices.", choice1, choice2, choice3);
	
			over = playCard(handpos, choice1, choice2, choice3, &G);
			if (over) {
				printf("\nFailed to play %d.\n", currCard);
			} else {
				printf("Successfuly played '%d' card.\n", currCard);
				printf("Current state is as follows:\n");
				for ( i = 0; i < players; i++) {
					showhand(G, i);
					showdeck(G, i);
					showdiscard(G, i);
					printf("\n");
				}
			}
		}

		//Buying Phase
		printf("\n=======Buy Phase=======\n");
		while(G.numBuys != 0 && G.coins >= 2) {
			printf("Number of buys: %d\n", G.numBuys);

			randnum = floor(Random() * 27);
			if (randnum == 27) {
				randnum = 26;
			}

			printf("Player %d tries to buy %d.\n", curTurn, randnum);
			over = buyCard(randnum, &G);
			if (over == - 1) {
				printf("Failed to buy %d.\n", randnum);
			} else {
				printf("Successfully bought %d.\n", randnum);
			}
		}

		//End Phase
		printf("\n=======End Phase=======\n");
		endTurn(&G);
		printf("End of turn.\n\n");

		over = isGameOver(&G);

		if (over == 1) {
			printf("\n*******GAME OVER*******\n");
			
			getWinners(winners, &G);
			printf("\nThe winner is: ");
			for (i = 0; i < 4; i ++) {
				if (winners[i] == 1) {
					printf("%d\n", i);
					break;
				}
			}

			printf("Final Scores: \n");
			for (i = 0; i < 4; i++) {
				printf("Player %d: %d\n", i, scoreFor(i, &G));
			}
			printf("\n**********************\n");
			break;
		}
	}	

	return 0;
}
